home *** CD-ROM | disk | FTP | other *** search
- ;********************************************************
- ;* *
- ;* DrvSend *
- ;* *
- ;* Function: Split the input whole block into *
- ;* some packets and send its using *
- ;* IPX services. *
- ;* Input: SS:BP points to registers save *
- ;* area. Select from this area CX, *
- ;* and DS:DX. In CX's length of segment, *
- ;* DS:DX points start of segment. *
- ;* Output: In AX places IPX return code or zero *
- ;* if all O.K! *
- ;* *
- ;* *
- ;* CopyRight 1995. Nicholas Poljakov all rights reserved.*
- ;* *
- ;********************************************************
- .MODEL TINY
- .DOSSEG
-
- include c:\lu62\novell\inc\ipxhdr.inc
- include c:\lu62\novell\inc\seg.inc
-
- EXTRN ipxProc : DWORD
- EXTRN CancelECB : PROC
- EXTRN PrepECB : PROC
- EXTRN ipxECB : BYTE
- EXTRN ActLuMsg : BYTE
- EXTRN LocalS : BYTE
-
- PUBLIC DrvSend, CurSeg, SndStart, MainCycl
- PUBLIC SndExit, SndBlk, LastBlk, CallIPX, PollInUse
- PUBLIC SetNtAddr, NextBlk
- PUBLIC LocSnd, SndCont
- PUBLIC SetSAddr, SBExit
- PUBLIC InfoMsg, TestBcs, CmpCycl, SetExit
-
- BLKLT EQU 546 ; length of IPX max. block
-
- .CODE
- DrvSend PROC
- jmp SndStart
-
- CurSeg DD 0 ; pointer to current segment
- ipxSECB IPXECB <> ; IPX ECB area
- ipxHDR IPXHDR <> ; IPX header area
-
- SndStart:
- cmp LocalS, 0 ; is it a "Local_Send" operation ?
- jne LocSnd
-
- les bx, DWORD PTR [bp + 8] ; input DS:DX pointer
- mov cx, WORD PTR [bp + 12] ; input CX value
- jmp short SndCont
-
- LocSnd:
- mov bx, OFFSET ActLuMsg
- mov cx, PRFLT + 9
-
- SndCont:
- mov dx, cx
- sub dx, PRFLT
- cmp es:[bx].SegLen, dx
- je MainCycl
- mov ax, -1 ; error return code (wrong length of segment)
- jmp SndExit
- MainCycl:
- mov WORD PTR CurSeg, bx ; save pointer
- mov ax, es ; to
- mov WORD PTR CurSeg + 2, ax ; current segment
- call SetNtAddr
- and ax, ax ; check return code
- jnz SndExit ; bad return code...
- call NextBlk
- call SndBlk ; prepare IPX fields and send block
- and ax, ax
- jnz SndExit ; bad return code fron IPX
- les bx, CurSeg
- les bx, es:[bx].SegLink ; pointer to next segment
- ; if it present.
- mov ax, es
- and ax, ax ; if NULL pointer
- jnz MainCycl ; then
- and bx, bx ; exit
- jnz MainCycl ; from procedure
-
- call PrepECB ; set "listen" mode for receiving
-
- SndExit:
- clc
- ret
- DrvSend ENDP
-
- SndBlk PROC
- ;*
- ;* On input : CX - total length of block; ES:BX - pointer to
- ;* block.
- ;*
- push cx
-
- ; First, sets ECB fields
-
- mov ipxSECB.SocNum, MY_SOCKET
- mov ipxSECB.FragNum, 2 ; two fragments : IPX header and
- ; data segment.
-
- mov ax, OFFSET ipxHDR
- mov WORD PTR ipxSECB.FAddr, ax
- mov ax, cs
- mov WORD PTR ipxSECB.FAddr + 2, ax
- mov ipxSECB.FLt, 30 ; header length
-
- SetSAddr:
- mov WORD PTR ipxSECB.SAddr, bx
- mov ax, es
- mov WORD PTR ipxSECB.SAddr + 2, ax
- cmp cx, BLKLT
- jb LastBlk
- mov ipxSECB.SLt, BLKLT ; header length
- mov ax, BLKLT + 30
- xchg ah, al
- mov ipxHDR.PLt, ax ; length of IPX header and max. block
- ; length
- add bx, BLKLT ; pointer to next segment of message
- sub cx, BLKLT ; rest length of message
- jmp short CallIPX
- LastBlk:
- mov ipxSECB.SLt, cx ; header length
- xor cx, cx ; End_Of_Block identifyer
-
- ; Set total length of packet
-
- mov ax, ipxSECB.SLt
- add ax, ipxSECB.FLt
- xchg ah, al
- mov ipxHDR.PLt, ax
-
- ; Then, call IPX send service...
-
- CallIPX:
- push cx ; save CX from modification
- mov bx, cs
- mov es, bx
- mov bx, 3
- mov si, OFFSET ipxSECB
- call ipxProc
-
- ; Wait for complete of SEND function
-
- sti ; enable interrupts
- PollInUse:
- cmp ipxSECB.InUse, 0
- jnz PollInUse
-
- pop cx
- and cx, cx ; have I some data for sending yet?
- jz SBExit
- jmp SetSAddr ; set address of next data fragment and
- ; try again...
- SBExit:
- xor ah, ah
- mov al, ipxSECB.RetCode ; set return code
-
- pop cx
- ret
- SndBlk ENDP
-
- SetNtAddr PROC
-
- ; Set network address in ECB
- ; ES:BX points to start of input segment.
-
- push cx
- mov ax, WORD PTR es:[bx]
- mov WORD PTR ipxSECB.PAddr, ax
- mov ax, WORD PTR es:[bx + 2]
- mov WORD PTR ipxSECB.PAddr + 2, ax
- mov ax, WORD PTR es:[bx + 4]
- mov WORD PTR ipxSECB.PAddr + 4, ax
-
- ; Set network address in header
-
- mov ax, WORD PTR es:[bx]
- mov WORD PTR ipxHDR.NdAddr, ax
- mov ax, WORD PTR es:[bx + 2]
- mov WORD PTR ipxHDR.NdAddr + 2, ax
- mov ax, WORD PTR es:[bx + 4]
- mov WORD PTR ipxHDR.NdAddr + 4, ax
-
- ; Set destignated socket
-
- mov ipxHDR.SkDest, MY_SOCKET
-
- ; Set packet type
-
- cmp LocalS, 0
- je InfoMsg
- mov ipxHDR.PType, 0 ; it's a control message
- jmp short TestBcs
- InfoMsg:
- mov ipxHDR.PType, 4 ; it's a information message
-
- ; Test if it broadcasting message...
- TestBcs:
-
- xor si, si
- mov cx, 6
- CmpCycl:
- cmp BYTE PTR es:[bx + si], 0ffh ; Node address
- jne SetExit ; == 0fffffffffffh
- inc si ; ???
- loop CmpCycl
-
- call CancelECB ; cancel listen if so...
-
- SetExit:
- xor ax, ax
- pop cx
- ret
- SetNtAddr ENDP
-
- NextBlk PROC
- push cx
- mov ax, bx
- mov cx, 4
- shr ax, cl
- mov di, es
- add ax, di
- mov es, ax
- and bx, 000fh
- pop cx
- ret
- NextBlk ENDP
-
- END
-